; 编译链接方法

;nasm -f elf -o kernel.o kernel.asm
;gcc -c -o main.o main.c
;ld -s -Ttext 0x30400  -o kernel.bin kernel.o main.o font.o lib.o


;常量定义
selectorKernelCs  equ 8


extern  main    ;引入c编写的主函数  main.c 中主函数
extern  initGdt ;初始化新的gdt
extern  gdtPtr  ;保存gdt 基地址和偏移地址 在main.c 中定义

; 内核堆栈段定义
[section .bss]
stackSpace  resb   2*1024    ;2k
stackTop:                    ;栈顶

; 内核代码段
[section .text]	             ; 代码段
global _start	             ; 导出 _start
global init                  ;
global io_hlt                ; 导出 _io_hlt  这里前边不用加下滑线
global io_cli                ;
global io_sti                ;
global io_stihlt             ;
global io_in8                ;
global io_in16               ;
global io_in32               ;
global io_out8               ;
global io_out16              ;
global io_out32              ;
global io_load_eflags        ;
global io_store_eflags       ;

; 跳到这里来的时候
_start:       
        mov esp ,stackTop ;从loader 中把堆栈切换到kernel 中
	sgdt [gdtPtr]  ;保存gdt 到全局变量 gdtPtr

	call initGdt   ;初始化gdt
	lgdt [gdtPtr]  ;重新加载新的gdt 
	jmp selectorKernelCs:init ;切换到新的代码段上

init:
        call main      ;调用c 中主函数


; void io_hlt() 停机函数,c 中没有功能实现hlt 指令
io_hlt: 
        hlt
        ret

;void io_cli()
io_cli:
        cli
	ret

;void io_sti()
io_sti:
        sti
	ret

;void io_stihlt()
io_stihlt:
        sti
	hlt
	ret

;int io_in8(int port)
io_in8:
       mov edx ,[esp+4] ;取port
       mov eax ,0       ;返回值清零
       in  al  ,dx
       ret

;int io_in16(int port)
io_in16:
       mov edx ,[esp+4] ;取port
       mov eax ,0       ;返回值清零
       in  ax  ,dx
       ret

;int io_in32(int port)
io_in32:
       mov edx ,[esp+4] ;取port
       mov eax ,0       ;返回值清零
       in  eax  ,dx
       ret

; void io_out8(int port,int data)
io_out8:
       mov edx,[esp+4]
       mov al ,[esp+8]
       out dx,al
       ret

; void io_out16(int port,int data)
io_out16:
       mov edx ,[esp+4]
       mov eax ,[esp+8]
       out dx,ax
       ret

; void io_out32(int port,int data)
io_out32:
       mov edx ,[esp+4]
       mov eax ,[esp+8]
       out dx,eax
       ret
;int io_load_eflags()
io_load_eflags:
       pushfd
       pop eax
       ret
;void io_store_eflags(int eflags)
io_store_eflags:
       mov  eax,[esp+4]
       push eax
       popfd
       ret
